package com.dimld.utils;


import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.net.ssl.*;
import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLConnection;
import java.nio.charset.StandardCharsets;
import java.security.KeyManagementException;
import java.security.NoSuchAlgorithmException;
import java.security.cert.X509Certificate;
import java.util.List;
import java.util.Map;

public class HttpFun {
    private static final Logger log = LoggerFactory.getLogger("ROOT");

    /**
     * 向指定URL发送GET方法的请求
     *
     * @param url    发送请求的URL
     * @param params 请求参数，请求参数应该是 name1=value1&name2=value2 的形式。
     * @return URL 所代表远程资源的响应结果
     */
    public static String get(String url, String params) {
        log.debug("get url:" + url + " param:" + params);
        StringBuilder  result = new StringBuilder();
        BufferedReader in     = null;
        try {
            String urlNameString;
            if (params != null && !params.trim().equals("")) {
                urlNameString = url + "?" + params;
            } else {
                urlNameString = url;
            }
            URL realUrl = new URL(urlNameString);
            // 打开和URL之间的连接
            URLConnection connection = realUrl.openConnection();
            // 设置通用的请求属性
            connection.setRequestProperty("accept", "*/*");
            connection.setRequestProperty("connection", "Keep-Alive");
            connection.setRequestProperty("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.1;SV1)");
            // 建立实际的连接
            connection.connect();
            // 获取所有响应头字段
            Map<String, List<String>> map = connection.getHeaderFields();
            // 遍历所有的响应头字段
            for (String key : map.keySet()) {
                System.out.println(key + "--->" + map.get(key));
            }
            // 定义 BufferedReader输入流来读取URL的响应
            in = new BufferedReader(new InputStreamReader(connection.getInputStream()));
            String line;
            while ((line = in.readLine()) != null) {
                result.append(line);
            }
        } catch (Exception e) {
            log.error("异常", e);
        }
        // 使用finally块来关闭输入流
        finally {
            try {
                if (in != null) {
                    in.close();
                }
            } catch (Exception e2) {
                e2.printStackTrace();
            }
        }
        log.debug("回执结果:" + result);
        return result.toString();
    }

    /**
     * 发送HttpPost请求
     *
     * @param url    服务地址
     * @param params json字符串,例如: "{ \"id\":\"12345\" }" ;其中属性名必须带双引号<br/>
     * @return 成功:返回json字符串<br/>
     */
    public static String post(String url, String params) {
        try {
            log.debug("post url:" + url + " params:" + params);
            URL               raelUrl = new URL(url);// 创建连接
            HttpURLConnection conn    = (HttpURLConnection) raelUrl.openConnection();
            conn.setDoOutput(true);
            conn.setDoInput(true);
            conn.setUseCaches(false);
            conn.setInstanceFollowRedirects(true);
            conn.setRequestMethod("POST"); // 设置请求方式
            conn.setRequestProperty("Accept", "application/json"); // 设置接收数据的格式
            conn.setRequestProperty("Content-Type", "application/json"); // 设置发送数据的格式
            conn.setConnectTimeout(1000);
            conn.connect();
            OutputStreamWriter out = new OutputStreamWriter(conn.getOutputStream(), StandardCharsets.UTF_8); // utf-8编码
            out.append(params);
            out.flush();
            out.close();
            // 读取响应
            InputStream    is     = conn.getInputStream();
            StringBuilder  sb     = new StringBuilder();
            BufferedReader reader = new BufferedReader(new InputStreamReader(is));
            String         line;
            while ((line = reader.readLine()) != null) {
                sb.append(line);
            }
            String result = sb.toString();
            log.debug("回执结果:" + result);
            return result;
        } catch (IOException e) {
            log.error("推送异常：{}，{}，{}",url,params,e);
            e.printStackTrace();
        }
        return "error"; // 自定义错误信息
    }

    public static String postForm(String url, String params) {
        try {
            log.debug("post url:" + url + " params:" + params);
            URL               raelUrl = new URL(url);// 创建连接
            HttpURLConnection conn    = (HttpURLConnection) raelUrl.openConnection();
            conn.setDoOutput(true);
            conn.setDoInput(true);
            conn.setUseCaches(false);
            conn.setInstanceFollowRedirects(true);
            conn.setRequestMethod("POST"); // 设置请求方式
            conn.setRequestProperty("Accept", "application/json"); // 设置接收数据的格式
            conn.setRequestProperty("Content-Type", "x-www-form-urlencoded"); // 设置发送数据的格式
            conn.setConnectTimeout(1000);
            conn.connect();
            OutputStreamWriter out = new OutputStreamWriter(conn.getOutputStream(), StandardCharsets.UTF_8); // utf-8编码
            out.append(params);
            out.flush();
            out.close();
            // 读取响应
            InputStream    is     = conn.getInputStream();
            StringBuilder  sb     = new StringBuilder();
            BufferedReader reader = new BufferedReader(new InputStreamReader(is));
            String         line;
            while ((line = reader.readLine()) != null) {
                sb.append(line);
            }
            String result = sb.toString();
            log.debug("回执结果:" + result);
            return result;
        } catch (IOException e) {
            log.error("推送异常：{}，{}，{}",url,params,e);
            e.printStackTrace();
        }
        return "error"; // 自定义错误信息
    }

    public static void main(String[] args) {
        System.out.println(postForm("http://10.162.1.45:95/Services/HT_Service.asmx","{\"phoneNumber\":\"95144111\",\"callTransferStartTime\":\"2021-10-08 18:45:24\",\"callTransferEndTime\":\"2021-10-08 18:45:30\",\"callTransferStatus\":\"0\",\"callWaitTime\":\"5266\",\"callDisconnectStatus\":\"2\"}"));
    }
    private static class TrustAnyTrustManager implements X509TrustManager {

        public void checkClientTrusted(X509Certificate[] chain, String authType) {
        }

        public void checkServerTrusted(X509Certificate[] chain, String authType) {
        }

        public X509Certificate[] getAcceptedIssuers() {
            return new X509Certificate[]{};
        }
    }

    private static class TrustAnyHostnameVerifier implements HostnameVerifier {
        public boolean verify(String hostname, SSLSession session) {
            return true;
        }
    }

    /**
     * post方式请求服务器(https协议)
     *
     * @param url     请求地址
     * @param content 参数
     * @param charset 编码
     * @return
     * @throws NoSuchAlgorithmException
     * @throws KeyManagementException
     * @throws IOException
     */
    public static String postHttps(String url, String content, String charset)
            throws NoSuchAlgorithmException, KeyManagementException, IOException {
        SSLContext sc = SSLContext.getInstance("SSL");
        sc.init(null, new TrustManager[]{new TrustAnyTrustManager()}, new java.security.SecureRandom());

        URL                console = new URL(url);
        HttpsURLConnection conn    = (HttpsURLConnection) console.openConnection();
        conn.setSSLSocketFactory(sc.getSocketFactory());
        conn.setHostnameVerifier(new TrustAnyHostnameVerifier());
        conn.setDoOutput(true);
        conn.setRequestProperty("Accept", "application/json"); // 设置接收数据的格式
        conn.setRequestProperty("Content-Type", "application/json"); // 设置发送数据的格式
        conn.connect();
        DataOutputStream out = new DataOutputStream(conn.getOutputStream());
        out.write(content.getBytes(charset));
        // 刷新、关闭
        out.flush();
        out.close();
        InputStream is = conn.getInputStream();
        if (is != null) {
            ByteArrayOutputStream outStream = new ByteArrayOutputStream();
            byte[]                buffer    = new byte[1024];
            int                   len;
            while ((len = is.read(buffer)) != -1) {
                outStream.write(buffer, 0, len);
            }
            is.close();
            return new String(outStream.toByteArray(), StandardCharsets.UTF_8);
        }
        return null;
    }

}
